#pragma once

#include <vector>
#include "hnswlib/hnswalg.h"
#include "hnswlib/hnswlib.h"
#include "index_factory.h"

class HNSWLibIndex {
public:
    /**
     * @brief constructor
     * @param[in] dim int 
     * @param[in] num_data 
     * @param metric the maximum of  
     * @param ef_construction The priority queue size when the index is built 
     */
    HNSWLibIndex(int dim, int num_data, IndexFactory::MetricType metric, 
            int M = 16, int ef_construction = 200);
    
    /**
     *brief 
     *param[in] data
     *param[in] label
     */
    void insert_vectors(const std::vector<float>& data, uint64_t label);
    
    /**
     * @brief search
     * @param[in] query
     * @param[in] k
     * @param[in] ef_search The priority queue size 
     * @return 
     */
    std::pair<std::vector<long>, std::vector<float>>
        search_vectors(const std::vector<float>&query, int k, int ef_search = 50);

private:
    int dim;
    // use to caculate the similiarity  
    hnswlib::SpaceInterface<float>* space;
    // HNSW index itself, used to store data and execute query 
    hnswlib::HierarchicalNSW<float>* index;
};
